#include <iostream>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <cstring>
#include <string>
#define SIZE 1024

//子进程写入数据部分
std::string getOtherMessage()
{
    //消息次数
    static int cnt = 0;
    std::string message = std::to_string(cnt);
    cnt++;
    //子进程的pid
    pid_t self_id  = getpid();
    std::string stringpid = std::to_string(self_id);

    std::string info = "messageid: ";
    message += " My pid is :";
    message += stringpid;

    return message;
}
void SubProcessWrite(int wfd)
{
    int pipesize = 0;
    std::string message = "Father,I am your son process! ";
    char charactor = 'A';
    while(true)
    {
        std::cout << "+++++++++++++++++++++++++++++++++++++++++++++++++" << std::endl;
        //得到数据
        std::string info = message + getOtherMessage();
        //开始写入数据
        write(wfd,info.c_str(),info.size());
        std::cerr << info << std::endl;
        
        sleep(1);

        write(wfd,&charactor,1);
        std::cout << "pipesize: " << ++pipesize << " write charactor is: " << charactor++ << std::endl;
        if(charactor == 'H') break;

    }
    std::cout  << "child quit……" << std::endl;
}
//父进程读取数据部分
void ProcessFatherRead(int rfd)
{
    char inbuffer[SIZE];
    while(true)
    {
        //休眠一会儿开始读取
        sleep(2);
        std::cout << "---------------------------------------------------" << std::endl;
        //sleep(500);
        ssize_t n = read(rfd,inbuffer,sizeof(inbuffer) - 1);
        if(n > 0)
        {
            inbuffer[n] = 0;// == '\0'
            std::cout << inbuffer << std::endl;
        }
        else if(n == 0) //如果n == 0代表读到了文件结尾
        {
            std::cout << "client quit, father get return val: " << n << " father quit tool" << std::endl;
            break; 
        }
        else if(n > 0)
        {
            std::cout << "Read error!" << std::endl;
            break;
        }
    }
}


int main()
{
    //1. 创建管道
    int pipefd[2];
    int n = pipe(pipefd);
    if(n)
    {
        std::cerr << "errno:" << errno << ":"\
        << "errstring is :" << strerror(errno) << std::endl; 
    }
    std::cout << "pipefd[0]:" << pipefd[0] << " pipefd[1]:" << pipefd[1] << std::endl;
    sleep(1);
    
    //2.创建子进程
    pid_t id = fork();
    if(id == 0)
    {
        //子进程开始准备工作
        std::cout << "子进程准备开始写入数据了..." << std::endl;
        sleep(1);
        close(pipefd[0]);
        
        SubProcessWrite(pipefd[1]);
        close(pipefd[1]);
        exit(0);
    }
    //3.父进程开始读取 
    std::cout << "父进程关闭不需要的fd, 准备接收消息了..." << std::endl;
    sleep(1);
    close(pipefd[1]);
    ProcessFatherRead(pipefd[0]);
    std::cout << "5s,father close fd" << std::endl;
    sleep(5);
    close(pipefd[0]);
    //4.父进程开始等待子进程
    int status = 0;
    pid_t rid = waitpid(id,&status,0);
    if(rid > 0)
    {
        std::cout << "wait child process done, exit sig: " << (status&0x7f) << std::endl;
        std::cout << "wait child process done, exit code(ign): " << ((status>>8)&0xff) << std::endl;
    }

    return 0;
}


// int main()
// {
//     pid_t id = fork();
//     if (id == 0)
//     {
//         close(0);
//         close(1);
//         close(2);
//         std::cout << "I am a child process!" << std::endl;

//     }
//     if(id > 0)
//     {
//         std::cout << "I am a father process!" << std::endl;
//     }

//     return 0;
// }